<template>
  <div class="alarmCurve">
    <div class="ventilation">
      <div class="main">
        <div class="title">主回风斜井主扇</div>
        <div class="content">
          <div class="col">
            <b-fan :status="0" name="一号机第一节"></b-fan>
            <b-fan :status="0" name="一号机第二节"></b-fan>
          </div>
          <div class="col">
            <b-fan :status="1" name="二号机第一节"></b-fan>
            <b-fan :status="1" name="二号机第二节"></b-fan>
          </div>
        </div>
      </div>
      <div class="local">
        <div class="title">局部通风机</div>
        <div class="content col">
          <b-fan :status="0" name="1213瓦斯鉴定巷2掘进工作面局部通风机备机第一节"></b-fan>
          <b-fan :status="0"></b-fan>
        </div>
      </div>
    </div>
    <div class="history-curve">
      <div class="info">
        <div class="info-item">
          <span>矿井供电：</span>
          <el-tag type="primary">正常</el-tag>
        </div>
        <div class="info-item">
          <span>人数曲线：</span>
          <el-switch v-model="searchData.peopleSwitch" />
        </div>
        <el-date-picker class="time-picker" v-model="searchData.timeRange" start-placeholder="开始时间"
          end-placeholder="结束时间" value-format="YYYY-MM-DD HH:mm:ss" type="datetimerange" />
      </div>

      <div class="content">
        <div class="left">
          <el-checkbox-group class="my-checkbox" v-model="searchData.checkedCdCode">
            <el-checkbox v-for="item in filterSensorList" :key="item.cdCode" :value="item.cdCode"
              :label="item.areaLocation" />
          </el-checkbox-group>
        </div>
        <!-- 右边图表区 -->
        <BEchart class="charts" :options="chartOption"></BEchart>
      </div>
    </div>
  </div>

</template>

<script setup lang="ts">
import { ref, computed, onMounted, watch } from 'vue'
import dayjs from 'dayjs'
import { ElMessage } from 'element-plus'
import { getHisGraph } from '@/api/sensor'
import { getNeedShowSensor } from '@/api/alarm'
import { getPersonData } from '@/api/person'
import { debounce } from 'lodash'
import BEchart from '@/components/b-echart/index.vue'
import { useAuthStore } from '@/store/auth'
import { storeToRefs } from 'pinia'
import BFan from '@/components/b-fan.vue'
interface ChartDataItem {
  dateMinute: string
  cdValue: number
  formatter: string
  cdState?: string
  cdStateName?: string
  showValue?: string
  unitCode?: string
  cdLocation?: string
}

interface ChartData {
  cdCode: string
  cdLocation: string
  data: ChartDataItem[]
  sensorType?: string
  maxValue?: number
  minValue?: number
  averageValue?: number
  unitCode?: string
  bjIndexs?: Array<[number, number]>
  bxIndexs?: Array<[number, number]>
}

interface SearchData {
  timeRange: [string, string]
  checkedCdCode: string[]
}

interface AreaLocation {
  cdCode: string
  areaLocation: string
}

interface LegendData {
  name: string
  maxValue?: number
  minValue?: number
  averageValue?: number
  unitCode?: string
}

interface ChartOption {
  color: string[]
  title: {
    text: string
    left: string
    textStyle: {
      color: string
    }
  }
  tooltip: {
    trigger: string
    formatter: (params: any) => string
  }
  legend: {
    top: string
    type: string
    left: string
    data: LegendData[]
    textStyle: {
      color: string
      fontSize: number
    }
    formatter?: (name: string) => string
  }
  grid: {
    top: string
    left: string
    right: string
    bottom: string
  }
  xAxis: {
    type: string
    axisLine: {
      lineStyle: {
        color: string
      }
    }
  }
  yAxis: {
    type: string
    name: string
    axisLine: {
      lineStyle: {
        color: string
      }
    }
  }
  series: any[]
  visualMap: any[]
}

const loading = ref(false)
const filterVal = ref('')
const sensorList = ref<AreaLocation[]>([])
const isMore24Hour = ref(false)
const eChartDataCache = ref<ChartData[]>([])
const curve_patching_duration_config = ref(60) // Default 60 seconds

const searchData = ref<SearchData>({
  timeRange: ['', ''],
  checkedCdCode: [],
  peopleSwitch: true
})

const chartOption = ref<ChartOption>({
  color: [
    '#FC9E40',
    '#C43CC4',
    '#ffff00',
    '#ffa500',
    '#0000FF',
    '#9400d3',
    '#9f79ee',
    '#696969',
    '#ff00ff',
    '#bdb76b',
    '#cd5c5c',
    '#006400',
    '#00bfff',
    '#66cd00',
    '#8b8989',
    '#ff1493'
  ],
  dataZoom: [
    {
      type: 'slider',
      show: true,
      bottom: 0,
      height: 20,
      moveHandleSize: 4,
      dataBackground: {
        areaStyle: {
          color: '#333',
          opacity: 0.3
        }
      }
    },
    {
      type: 'inside'
    },
    {
      type: 'slider',
      show: true,
      yAxisIndex: 0,
      filterMode: 'empty',
      height: '70%',
      showDataShadow: false,
      right: 4,
      width: 20,
      moveHandleSize: 4,
    }
  ],
  tooltip: {
    trigger: 'axis',
    formatter: (params: any) => {
      let result = ''
      if (Array.isArray(params)) {
        params.forEach((item: any, index: number) => {
          if (index === 0) {
            result += item.data.dateMinute + '<br>'
          }
          result += item.marker + item.data.formatter + '<br>'
        })
      }
      return result
    }
  },
  legend: {
    top: '0',
    type: 'plain',
    left: 'center',
    data: [],
    textStyle: {
      color: '#00FFA7',
      fontSize: 12
    }
  },
  grid: {
    top: '35',
    left: '8%',
    right: '60',
    bottom: '40'
  },
  xAxis: {
    type: 'time',
    axisLine: {
      show: true,
      lineStyle: {
        color: '#00FFA7',
      }
    },
  },
  yAxis: [
    {
      type: 'value',
      name: '监测值',
      axisLine: {
        show: true,
        lineStyle: {
          color: '#00FFA7',
        }
      },
      splitLine: {
        show: true,
        lineStyle: {
          color: '#0f5741',
        }
      },
    },
    {
      type: 'value',
      name: '人数曲线',
      axisLine: {
        lineStyle: {
          color: '#00FFA7',
        }
      },
      splitLine: {
        show: false,
      },
    }
  ],
  series: [],
  visualMap: []
})

const filterSensorList = computed(() => {
  return sensorList.value.filter((item) =>
    filterVal.value ? item.areaLocation.includes(filterVal.value) : true
  )
})

const clearECharts = () => {
  if (chartOption.value.legend) {
    chartOption.value.legend.data = []
  }
  chartOption.value.series = []
  chartOption.value.visualMap = []
}

const formatDate = (timestamp: number, format: string): string => {
  return dayjs(timestamp).format(format)
}

const isNotNull = (value: any): boolean => {
  return value !== null && value !== undefined
}

const getString = (value: any): string => {
  return value?.toString() || ''
}

const getHisGraphFun = debounce(async () => {
  if (!searchData.value.checkedCdCode.length) {
    ElMessage.error('请选择传感器')
    clearECharts()
    return
  }

  if (!searchData.value.timeRange.length) {
    ElMessage.error('请选择开始时间和结束时间')
    clearECharts()
    return
  }

  loading.value = true

  try {
    const { data } = await getHisGraph({
      cdCodes: searchData.value.checkedCdCode,
      startTime: searchData.value.timeRange[0],
      endTime: searchData.value.timeRange[1]
    })
    eChartDataCache.value = data.data
    isMore24Hour.value = data.isMore24Hour

    if (searchData.value.peopleSwitch) {
      const { data: personData } = await getPersonData({
        ...globalParams.value,
        startTime: searchData.value.timeRange[0],
        endTime: searchData.value.timeRange[1],
      })
      const list = personData.dataList.map(item => {
        return {
          cdLocation: '人数曲线',
          cdValue: item.count,
          showValue: item.count + '人',
          dateMinute: item.time
        }
      })
      eChartDataCache.value.push({
        cdLocation: '人数曲线',
        data: list
      })
    }
    showEChartData()
  } catch (error) {
    clearECharts()
  } finally {
    loading.value = false
  }
}, 500)

const showEChartData = () => {
  clearECharts()

  // 生成提示信息的函数
  const formatter = (data: ChartDataItem): string => {
    let s = data.cdLocation || ''

    if (isNotNull(data.cdValue)) {
      s += ' ' + data.showValue
    }

    // 不正常
    if (getString(data.cdState) !== '0') {
      s += ' ' + getString(data.cdStateName)
    }

    return s
  }
  // 生成报警或标校数据的函数
  const piecesFun = (pieces: any[], data: Array<[number, number]>, color: string) => {
    data.forEach((item) => {
      const itemLength = item.length
      if (itemLength === 1) {
        pieces.push({
          gte: new Date(item[0]).getTime(),
          lte: new Date(item[0]).getTime(),
          color: color
        })
      } else if (itemLength > 1) {
        pieces.push({
          gte: new Date(item[0]).getTime(),
          lte: new Date(item[1]).getTime(),
          color: color
        })
      }
    })
  }

  const obj: Record<string, number> = {} // 用来去重的对象
  for (let i = 0; i < eChartDataCache.value.length; i++) {
    const { data, sensorType, cdLocation, bjIndexs, bxIndexs } =
      eChartDataCache.value[i]
    // 开关的特殊处理
    chartOption.value.legend.data.push({
      name: cdLocation
    })
    
    let step: boolean | 'start' = false
    if (sensorType && sensorType.substr(0, 1) !== '0') {
      step = 'start'
    }
    let yAxisIndex = 0
    if (cdLocation === '人数曲线') {
      yAxisIndex = 1
    }
    // 增加tag和初始化series
    chartOption.value.series.push({
      type: 'line',
      name: cdLocation,
      data: [],
      symbol: 'none',
      lineStyle: {
        width: 2
      },
      yAxisIndex,
      step
    })

    
    // 标校 报警
    if ((bjIndexs && bjIndexs.length) || (bxIndexs && bxIndexs.length)) {
      const pieces: any[] = []

      if (bjIndexs && bjIndexs.length) {
        const bxValues = bjIndexs.map((scope: [number, number]) => {
          const arr = [data[scope[0]].dateMinute]
          if (scope[1] !== undefined) {
            arr.push(data[scope[1]].dateMinute)
          }
          return arr
        })
        piecesFun(pieces, bxValues, '#EF585C')
      }
      if (bxIndexs && bxIndexs.length) {
        const bxValues = bxIndexs.map((scope: [number, number]) => {
          const arr = [data[scope[0]].dateMinute]
          if (scope[1] !== undefined) {
            arr.push(data[scope[1]].dateMinute)
          }
          return arr
        })
        piecesFun(pieces, bxValues, '#73EA5E')
      }

      chartOption.value.visualMap.push({
        type: 'piecewise',
        show: false,
        seriesIndex: i,
        dimension: 0,
        pieces,
        outOfRange: {
          color: chartOption.value.color[i % 15],
          symbolSize: [0]
        }
      })
    }

    for (let x = 0; x < data.length; x++) {
      const obj = data[x]
      const preObj = data[x - 1]

      if (preObj) {
        const s = dayjs(obj.dateMinute).diff(dayjs(preObj.dateMinute), 'second')
        if (s > 60) {
          for (let index = 0; index < Math.ceil(s / 60); index++) {
            const time = dayjs(obj.dateMinute).add(60, 'second').format('YYYY-MM-DD HH:mm:ss')
            chartOption.value.series[i].data.push({
              value: [time, null],
              dateMinute: time,
              formatter: formatter(obj)
            })
          }
        }
      }
      chartOption.value.series[i].data.push({
        value: [obj.dateMinute, obj.cdValue],
        dateMinute: obj.dateMinute,
        formatter: formatter(obj)
      })
    }
  }
}

const authStore = useAuthStore()
const { globalParams } = storeToRefs(authStore)
onMounted(() => {
  getNeedShowSensor(globalParams.value.cdCode).then((res) => {
    sensorList.value = res.data
  })
  searchData.value.timeRange = [globalParams.value.startTime, globalParams.value.endTime]
  searchData.value.checkedCdCode = [globalParams.value.cdCode]
  getHisGraphFun()

  watch(
    searchData.value,
    () => {
      getHisGraphFun()
    },
    {
      deep: true
    }
  )
})
</script>

<style lang="scss" scoped>
.alarmCurve {
  height: 300px;
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  background: var(--bg-color-page);
  padding: 8px;
  overflow: hidden;

  .header {
    display: flex;
    justify-content: space-between;
    align-items: center;
    height: 35px;
    width: 100%;

    .title {
      min-width: 286px;
      line-height: 35px;
      padding-left: 14px;
      padding-right: 100px;
      height: 35px;
      background-image: url(/src/assets/images/bdialog/title-bg.png);
      background-size: 100% 100%;
      white-space: nowrap;
      overflow: hidden;
      text-overflow: ellipsis;
    }
  }

  .ventilation {
    display: flex;
    gap: 8px;

    .main,
    .local {
      position: relative;
      background: var(--bg-color-page);
      padding: 8px 20px 8px 50px;

      .title {
        position: absolute;
        width: 40px;
        top: 50%;
        left: 0px;
        color: var(--text-color);
        font-weight: bold;
        transform: translateY(-50%);
        padding: 15px 12px;
        border-radius: 0 20px 20px 0;
        background-color: var(--el-color-primary-light-5);
      }

      .content {
        display: flex;
        width: 100%;
        height: 100%;
        gap: 16px;
      }

      .col {
        display: flex;
        flex-direction: column;
        justify-content: space-around;
      }
    }
  }

  .history-curve {
    display: flex;
    flex-direction: column;
    flex: 1;
    height: 100%;
    overflow: hidden;
    gap: 8px;

    .info {
      display: flex;
      align-items: center;
      gap: 16px;
      background: var(--bg-color-page);
      padding: 8px;

      .info-item {
        display: flex;
        align-items: center;
      }

      .sensor-type-checkbox {
        height: 240px;
        overflow-y: auto;
        flex-direction: column;
      }

      .sensor-input {
        width: 180px;
        margin: 0 8px 0 4px;
      }

      .time-picker {
        flex: 1;
        max-width: 300px;
      }
    }

    .content {
      display: flex;
      flex: 1;
      overflow: hidden;
      padding: 8px;
      background: var(--bg-color-page);

      .left {
        margin-top: 8px;
        height: calc(100% - 8px);
        flex-shrink: 0;
        overflow-y: auto;
        padding-right: 8px;
        .my-checkbox {
          flex-direction: column;

          .el-checkbox {
            margin-right: 0;
            color: var(--text-color-placeholder)
          }
        }
      }

      .charts {
        flex: 1;
        overflow: hidden;
      }
    }
  }
}
</style>
